--OOPTest             Johannes Karder, 2011-11-10
--Test program for the hydrac pseudocode compiler

program OOPTest

  type
    Base = class
      private a: real
      public b: real

      --constructors must have same name as the
      --containing class. hydrac compiles the
      --name to "Init" (needed for pascal only)
      public Base(in a: real in b: real)
      public GetA(): real
      public override PrintB()
    end

    Derived = class based on Base
      public Derived(in a: real in b: real)
      GetB(): real
      public override PrintB()
      public Pow(in a: real in b: real): real
      public Root(in a: real in b: real): real
    end

  --constructor
  Base.Base(in a: real in b: real)
  begin
    this->a := a
    this->b := b
  end Base

  Base.GetA(): real
  begin
    return this->a
  end GetA

  Base.PrintB()
  begin
    Write(in "Base.PrintB: " in this->b)
  end PrintB

  --constructor
  Derived.Derived(in a: real in b: real)
  begin
    inherited.Base(in a in b)
  end Math

  Derived.GetB(): real
  begin
    return this->b
  end GetB

  Derived.PrintB()
  begin
    Write(in "Derived.PrintB: " in this->b)
  end PrintB

  Derived.Pow(in a: real in b: real): real
    var
      res: real
  begin
    res := a
    while (b > 1) do
      res := res * a
      b := b - 1
    end
    return res
  end Pow

  Derived.Root(in a: real in b: real): real
    var
      i: int
      res: real
  begin
    res := a / 2
    for i := 1 to 1000 do
      res := ((b - 1) * this->Pow(in res in b) + a) / (b * this->Pow(in res in b - 1))
    end
    return res
  end Root

  var
    m1: ->Derived
    m2: ->Derived
    m3: ->Base

begin
  m1 := New(in Derived)
  Write(in "2^16 = " in m1->Pow(in 2 in 16))
  m2 := New(in Derived in 3 in 4)
  Write(in "16th root of 65536 = "
        in m2->Root(in 65536 in 16))
  Dispose(in m1)
  m3 := New(in Base in 5 in 6)
  m3->PrintB() --calls Base.PrintB()
  Dispose(in m3)
  m3 := m2
  m3->PrintB() --calls Derived.PrintB()
  Dispose(in m2)
end
